﻿using System;
using System.Data;
using System.Linq;
using System.Windows.Forms;
using Telerik.WinControls.UI;
using Zvezda.FSO2.DB;

namespace FSO
{
    public partial class FormPaymentOut : Form, InterfaceObjDeleteableForm
    {
        private DataSetFSO.PAYMENT_OUTRow _rowPayOut;
		public bool AllowSave;
        //private bool _rowIsNew;



        public FormPaymentOut()
        {
            InitializeComponent();
            //_rowIsNew = true;

            _rowPayOut = dataSetFSO1.PAYMENT_OUT.NewPAYMENT_OUTRow();
            dataSetFSO1.PAYMENT_OUT.AddPAYMENT_OUTRow(_rowPayOut);

            _rowPayOut.DATE = DateTime.Now.Date;
        }

        public FormPaymentOut(DataSetFSO.PAYMENT_OUTRow row)
        {
            InitializeComponent();
            //_rowIsNew = false;
            paymenT_OUTTableAdapter1.FillByID(dataSetFSO1.PAYMENT_OUT, row.ID);
            _rowPayOut = dataSetFSO1.PAYMENT_OUT.FindByID(row.ID);

            this.Text = "Платеж № " + _rowPayOut.NUMBER;
        }

        #region InterfaceObjDeleteableForm Members

        public int Delete()
        {
            _rowPayOut.Delete();  
            paymenT_OUTTableAdapter1.Update(_rowPayOut);
            this.Close();
            return 0;
        }

        #endregion

        #region IntefaceObjectForm Members

        public int Save()
        {
            //Такое значение возвратится, если сохранение не произошло
            int nRowsUpdatedCount = -1;

            if (_rowPayOut.IsNUMBERNull())
            {
                MessageBox.Show(this, "Не заполнено обязательное поле \"Номер\".\nИзменения не будут сохранены", "Обязательное поле", MessageBoxButtons.OK, MessageBoxIcon.Warning);
            }
            else
            {
                nRowsUpdatedCount = paymenT_OUTTableAdapter1.Update(_rowPayOut);
                foreach (DataSetFSO.PAY_OUT_ON_INV_INRow row in dataSetFSO1.PAY_OUT_ON_INV_IN.Rows)
                {
                    if (row.RowState == DataRowState.Added)
                        row.PAYMENT_OUT_ID = _rowPayOut.ID;
                }
                paY_OUT_ON_INV_INTableAdapter1.Update(dataSetFSO1.PAY_OUT_ON_INV_IN);
                //_rowIsNew = false;
                this.RefreshForm();
            }

            return nRowsUpdatedCount;
        }

        public int RefreshForm()
        {
            int result = 0;
            paY_OUT_ON_INV_INTableAdapter1.FillByPayOutID(dataSetFSO1.PAY_OUT_ON_INV_IN, _rowPayOut.ID);
            this.BindControls();
            return result;
        }

        public string FormName
        {
            get
            {
                string returnString = "Payment_out_";

                if (_rowPayOut.ID == -1)
                {
                    returnString = returnString + DateTime.Now;
                }
                else
                {
                    returnString = returnString + _rowPayOut.ID;
                }

                return returnString;
            }
        }

        #endregion

        private void FormPaymentOut_Load(object sender, EventArgs e)
        {
            GridViewTextBoxColumn colRegNum = new GridViewTextBoxColumn("REG_NUM", dataSetFSO1.PAY_OUT_ON_INV_IN.INV_RG_NUMBERColumn.ColumnName);
            colRegNum.HeaderText = "Рег. №";
            colRegNum.ReadOnly = true;

            GridViewDecimalColumn colPSumRub = new GridViewDecimalColumn("SUM_RUB", dataSetFSO1.PAY_OUT_ON_INV_IN.SUM_RUBColumn.ColumnName);
            colPSumRub.HeaderText = "Сумма списания(руб.)";
            colPSumRub.Minimum = 0;
            colPSumRub.FormatString = "{0:N2}";
            GridViewDecimalColumn colPSumCur = new GridViewDecimalColumn("SUM_CUR", dataSetFSO1.PAY_OUT_ON_INV_IN.SUM_CURColumn.ColumnName);
            colPSumCur.HeaderText = "Сумма списания(вал.)";
            colPSumCur.Minimum = 0;
            colPSumCur.FormatString = "{0:N2}";
            GridViewDecimalColumn colInvSum = new GridViewDecimalColumn("SUM_CUR_INV_IN", dataSetFSO1.PAY_OUT_ON_INV_IN.INV_SUMColumn.ColumnName);
            colInvSum.HeaderText = "Сумма";
            colInvSum.FormatString = "{0:N2}";
            colInvSum.ReadOnly = true;
            GridViewTextBoxColumn colCurrency = new GridViewTextBoxColumn("CURRENCY", dataSetFSO1.PAY_OUT_ON_INV_IN.CURRENCY_NAMEColumn.ColumnName);
            colCurrency.HeaderText = "Валюта";
            colCurrency.ReadOnly = true;
            GridViewDateTimeColumn colInvDate = new GridViewDateTimeColumn("DATE", dataSetFSO1.PAY_OUT_ON_INV_IN.INV_DATEColumn.ColumnName);
            colInvDate.HeaderText = "Дата выставления";
            colInvDate.FormatString = "{0:d}";
            colInvDate.ReadOnly = true;

            radGridViewInvIN.MasterTemplate.Columns.Clear();
            radGridViewInvIN.MasterTemplate.Columns.Add(colRegNum);
            radGridViewInvIN.MasterTemplate.Columns.Add(colPSumRub);
            radGridViewInvIN.MasterTemplate.Columns.Add(colPSumCur);
            radGridViewInvIN.MasterTemplate.Columns.Add(colInvSum);
            radGridViewInvIN.MasterTemplate.Columns.Add(colCurrency);
            radGridViewInvIN.MasterTemplate.Columns.Add(colInvDate);

            radGridViewInvIN.DataSource = dataSetFSO1.PAY_OUT_ON_INV_IN;

            dataSetFSO1.PAY_OUT_ON_INV_IN.ColumnChanged += new DataColumnChangeEventHandler(PAY_OUT_ON_INV_IN_ColumnChanged);
            this.RefreshForm();
        }

        //Будет вызываться для проверки правильности разноски платежа по счетам и пересчета соседней ячейки
        void PAY_OUT_ON_INV_IN_ColumnChanged(object sender, DataColumnChangeEventArgs e)
        {

            
            DataSetFSO.PAY_OUT_ON_INV_INRow poi = (DataSetFSO.PAY_OUT_ON_INV_INRow)e.Row;

            //Если изменили валютную ячейку
            if (e.Column.ColumnName == dataSetFSO1.PAY_OUT_ON_INV_IN.SUM_CURColumn.ColumnName)
            {
                //Высчитываем остаток
                decimal rest = FormInvoiceIn.GetRestWithoutItem(poi.INVOICE_IN_ID, poi.ID) - (poi.IsSUM_CURNull() ? 0 : poi.SUM_CUR);

                if (Decimal.Round(rest, 2) < 0)
                {
                    MessageBox.Show("Сумма счета меньше суммы всех платежей по нему!\n Проверьте правильность введенных данных ");

                    //Приравниваем подходящее значение ячейке ()
                    poi.SUM_CUR = poi.SUM_CUR + rest;
                }

                //пересчитываем соседнюю ячейку
                decimal rate = FormHelper.GetRate((String)poi.CURRENCY_NAME, _rowPayOut.DATE);
                if (rate > 0 && poi.SUM_RUB != poi.SUM_CUR * rate)
                {
                    poi.SUM_RUB = poi.SUM_CUR * rate;
                }

            }
            //если изменили рублевую ячейку
            else if (e.Column.ColumnName == dataSetFSO1.PAY_OUT_ON_INV_IN.SUM_RUBColumn.ColumnName)
            {
                if (Decimal.Round(this.GetRest(), 2) < 0)
                {
                    MessageBox.Show("Сумма платежа меньше суммы всех значений поля \"Сумма списания (руб.)\"!\n Проверьте правильность введенных данных ");

                    //Приравниваем подходящее значение ячейке ()
                    poi.SUM_RUB = poi.SUM_RUB + this.GetRest();
                }
                //пересчитываем соседнюю ячейку

                decimal rate = FormHelper.GetRate((String)poi.CURRENCY_NAME, _rowPayOut.DATE);
                if (rate > 0 && poi.SUM_CUR != poi.SUM_RUB / rate)
                {
                    poi.SUM_CUR = poi.SUM_RUB / rate;
                }

            }
        }

        

        private void BindControls()
        {
            //№ П\П
            radTextBoxNumber.DataBindings.Clear();
            radTextBoxNumber.DataBindings.Add("Text", _rowPayOut, dataSetFSO1.PAYMENT_OUT.NUMBERColumn.ColumnName, true, DataSourceUpdateMode.OnPropertyChanged);

            //Дата
            radDateTimePickerDate.DataBindings.Clear();
            radDateTimePickerDate.DataBindings.Add("Value", _rowPayOut, dataSetFSO1.PAYMENT_OUT.DATEColumn.ColumnName, true, DataSourceUpdateMode.OnPropertyChanged);
            
            //Сумма
            radMaskedEditBoxSum.DataBindings.Clear();
            radMaskedEditBoxSum.DataBindings.Add("Text", _rowPayOut, dataSetFSO1.PAYMENT_OUT.SUM_RUBColumn.ColumnName, true, DataSourceUpdateMode.OnPropertyChanged, 0, "N2");

            //Комментарии
            radTextBoxComment.DataBindings.Clear();
            radTextBoxComment.DataBindings.Add("Text", _rowPayOut, dataSetFSO1.PAYMENT_OUT.DESCRIPTIONColumn.ColumnName, true, DataSourceUpdateMode.OnPropertyChanged);
        }

        private void FormPaymentOut_FormClosing(object sender, FormClosingEventArgs e)
		{
			if (!AllowSave)
				return;
            if (_rowPayOut.RowState!= DataRowState.Deleted && _rowPayOut.RowState != DataRowState.Detached && (_rowPayOut.RowState == DataRowState.Added || _rowPayOut.RowState == DataRowState.Modified || (dataSetFSO1.PAY_OUT_ON_INV_IN.GetChanges()) != null))
            {
                DialogResult result = MessageBox.Show(this, "Были внесены изменения. Сохранить?", "Сохранить изменения?", MessageBoxButtons.YesNoCancel, MessageBoxIcon.Question);

                if (result == DialogResult.Yes)
                {
                    int SaveResult = this.Save();

                    if (SaveResult == -1)
                    {
                        e.Cancel = true;
                    }
                }
                else if (result == DialogResult.Cancel)
                {
                    e.Cancel = true;
                }
                else
                {
                    _rowPayOut.RejectChanges();
                }

            }
        }

        private void radButtonAddInv_Click(object sender, EventArgs e)
        {
            //делаем связь 1 счет - много платежей, но на всякий случай оставим в базе возмоность связи много ко многому - вдруг им захочется, достаточно буде убрать if
            if (dataSetFSO1.PAY_OUT_ON_INV_IN.Rows.Count > 0 || paY_OUT_ON_INV_INTableAdapter1.IsPayOutLinked(_rowPayOut.ID) > 0)
            {
                MessageBox.Show("Данный платеж уже привязан к другому счету, либо есть не сохраненные изменения (нажмите кнопку \"Сохранить\" и попробуйте снова)! ");
            }
            else
            {
                DialogFormSelectObject form = new DialogFormSelectObject(ObjctTypeEnum.INVOICE_IN);
                if (form.ShowDialog() == DialogResult.OK)
                {
                    foreach (GridViewRowInfo rowInf in form.SelectedRows)
                    {
                        DataRowView drv = (DataRowView)rowInf.DataBoundItem;
                        if (drv != null && drv.Row is DataSetFSO.VIEW_SEARCH_INVOICE_INRow)
                        {
                            DataSetFSO.VIEW_SEARCH_INVOICE_INRow invInRow = drv.Row as DataSetFSO.VIEW_SEARCH_INVOICE_INRow;

                            //Проверяем был ли добавлен платеж к счету
                            if ((from row in dataSetFSO1.PAY_OUT_ON_INV_IN select row.INVOICE_IN_ID).Contains(invInRow.ID))
                            {
                                MessageBox.Show("Данный счет уже был добавлен к платежу!");
                            }
                            else
                            {
                                DataSetFSO.PAY_OUT_ON_INV_INRow rowOrig = dataSetFSO1.PAY_OUT_ON_INV_IN.NewPAY_OUT_ON_INV_INRow();
                                dataSetFSO1.PAY_OUT_ON_INV_IN.AddPAY_OUT_ON_INV_INRow(rowOrig);
                                //rowOrig.PAYMENT_OUT_ID = _rowPayOut.ID;
                                rowOrig.INVOICE_IN_ID = (drv.Row as DataSetFSO.VIEW_SEARCH_INVOICE_INRow).ID;
                                if (!invInRow.IsREG_NUMBERNull())
                                    rowOrig.INV_RG_NUMBER = invInRow.REG_NUMBER;
                                if (!invInRow.IsSUMNull())
                                    rowOrig.INV_SUM = invInRow.SUM;
                                if (!invInRow.IsSHORT_NAME_CURRENCYNull())
                                    rowOrig.CURRENCY_NAME = invInRow.SHORT_NAME_CURRENCY;
                                if (!invInRow.IsDATENull())
                                    rowOrig.INV_DATE = invInRow.DATE;
                                //////////////////////////////////////
                                rowOrig.SUM_RUB = _rowPayOut.SUM_RUB;
                                /////////////////////////////////////
                            }
                        }
                    }
                }
            }
            //this.RefreshForm();
        }


        /*//Пересчет по курсу
         private void radGridViewInvIN_CellEndEdit(object sender, GridViewCellEventArgs e)
         {
            if (e.Column.Name == "SUM_CUR")
            {

                //Узнаем курс
                decimal rate = FormHelper.GetRate((String)e.Row.Cells["CURRENCY"].Value, _rowPayOut.DATE);

                try
                {
                    if (rate > 0)
                    {
                        e.Row.Cells["SUM_RUB"].Value = ((decimal)(e.Row.Cells["SUM_CUR"]).Value) * rate;
                    }
                }
                catch (InvalidCastException)
                {
                    //Если в пустую ячейку так ничего и не ввели
                }


            }
            else if (e.Column.Name == "SUM_RUB")
            {
                decimal rate = FormHelper.GetRate((String) e.Row.Cells["CURRENCY"].Value, _rowPayOut.DATE);

                try
                {
                    if (rate > 0)
                    {
                        e.Row.Cells["SUM_CUR"].Value = ((decimal)(e.Row.Cells["SUM_RUB"]).Value) / rate;
                    }
                }
                catch (InvalidCastException)
                {
                    //Если в пустую ячейку так ничего и не ввели
                }

            }
         }
     */
       
        //Свойство возвращает строку Invoice_in, на основе выделенной строчки в таблице счетов
        public DataSetFSO.INVOICE_INRow SelectedInvInRow
        {
            get
            {
                DataSetFSO.PAY_OUT_ON_INV_INRow tmp;
                DataSetFSO.INVOICE_INRow row;
                if (radGridViewInvIN.SelectedRows.Count > 0)
                {
                    tmp = (DataSetFSO.PAY_OUT_ON_INV_INRow)(((DataRowView)(radGridViewInvIN.SelectedRows.First()).DataBoundItem)).Row;
                    row = invoicE_INTableAdapter1.GetDataByID(tmp.INVOICE_IN_ID).FindByID(tmp.INVOICE_IN_ID);
                }
                else
                {
                    row = null;
                }
                return row;
            }
        }

        private void radGridViewInvIN_CellDoubleClick(object sender, GridViewCellEventArgs e)
        {
            DataSetFSO.INVOICE_INRow invInRow = this.SelectedInvInRow;
            if (invInRow != null)
            {

                FormInvoiceIn formPayOut = new FormInvoiceIn(invInRow);
                if (!FormHelper.HasOpenedForm(formPayOut.FormName))
                {
                    formPayOut.MdiParent = FormHelper.MainForm;
                    formPayOut.Show();
                    formPayOut.Select();
                }

            }
        }

        //возвращает остаток платежа
        private decimal GetRest()
        {
            return (_rowPayOut.IsSUM_RUBNull() ? 0 :_rowPayOut.SUM_RUB) - (from row in dataSetFSO1.PAY_OUT_ON_INV_IN select (row.IsSUM_RUBNull() ? 0 : row.SUM_RUB)).Sum();
        }

        //Возвращает остаток определенного платежа
        public static decimal GetRest(int PayID)
        {
            DataSetFSO.PAYMENT_OUTRow payOutRow;
            DataSetFSO.PAY_OUT_ON_INV_INDataTable dt;
            Zvezda.FSO2.DB.DataSetFSOTableAdapters.PAYMENT_OUTTableAdapter taPay = new Zvezda.FSO2.DB.DataSetFSOTableAdapters.PAYMENT_OUTTableAdapter();
            Zvezda.FSO2.DB.DataSetFSOTableAdapters.PAY_OUT_ON_INV_INTableAdapter taPoI = new Zvezda.FSO2.DB.DataSetFSOTableAdapters.PAY_OUT_ON_INV_INTableAdapter();

            payOutRow = taPay.GetDataByID(PayID).FindByID(PayID);
            dt = taPoI.GetDataByPayOutID(PayID);


            return (payOutRow.IsSUM_RUBNull() ? 0 : payOutRow.SUM_RUB) - (from row in dt select (row.IsSUM_RUBNull() ? 0 : row.SUM_RUB)).Sum();
        }

        public static decimal GetRestWithoutItem(int PayID, int? poiID)
        {
            DataSetFSO.PAYMENT_OUTRow payOutRow;
            DataSetFSO.PAY_OUT_ON_INV_INDataTable dt;
            Zvezda.FSO2.DB.DataSetFSOTableAdapters.PAYMENT_OUTTableAdapter taPay = new Zvezda.FSO2.DB.DataSetFSOTableAdapters.PAYMENT_OUTTableAdapter();
            Zvezda.FSO2.DB.DataSetFSOTableAdapters.PAY_OUT_ON_INV_INTableAdapter taPoI = new Zvezda.FSO2.DB.DataSetFSOTableAdapters.PAY_OUT_ON_INV_INTableAdapter();

            decimal rest = 0;

            payOutRow = taPay.GetDataByID(PayID).FindByID(PayID);
            dt = taPoI.GetDataByPayOutID(PayID);

            if (poiID != null)
            {
                rest = (payOutRow.IsSUM_RUBNull() ? 0 : payOutRow.SUM_RUB) - (from row in dt select ((row.IsSUM_RUBNull() || row.ID == poiID) ? 0 : row.SUM_RUB)).Sum();
            }
            else
            {
                rest = (payOutRow.IsSUM_RUBNull() ? 0 : payOutRow.SUM_RUB) - (from row in dt select (row.IsSUM_RUBNull() ? 0 : row.SUM_RUB)).Sum();
            }

            return rest;
        }

    }
}
